package com.uzai.console.aop;

import com.alibaba.fastjson.JSONObject;
import com.uzai.console.common.UzaiRespVo;
import com.uzai.console.dto.feign.uzaimanage.SysRunlogWarningDto;
import com.uzai.console.service.feign.UzaiManageFeignService;
import groovy.util.logging.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.StopWatch;

/**
 * @author liuqi
 * @date 2021年12月10日 15:04
 */
@Component
@Aspect
@Slf4j
public class TransactionAspect {
    private Logger logger = LoggerFactory.getLogger(TransactionAspect.class);

    @Autowired
    public UzaiManageFeignService uzaiManageFeignService;

    //切点
    @Pointcut("@annotation(org.springframework.transaction.annotation.Transactional)")
    public void transactionalCut(){}

    //环绕通知
    @Around("transactionalCut()")
    public Object around(ProceedingJoinPoint joinPoint) throws Throwable{
        Object result = null;
        Object target = joinPoint.getTarget();
        String methodName = joinPoint.getSignature().getName();
        StopWatch stopWatch = new StopWatch();

        try {//前置增强
            //logger.info(target.getClass().getName()+": The"+methodName+"method begins");
            stopWatch.start(target.getClass().getName()+"--"+methodName);
            result = joinPoint.proceed();
        }catch (Throwable e){////异常增强
            //logger.info(target.getClass().getName()+"：Exception of the method "+methodName+": "+e);
            throw e;
        }finally{//后置增强
            //logger.info(target.getClass().getName()+"：The "+methodName+" method ends.");
            stopWatch.stop();
           // logger.info("-获取事务接口分析：" + stopWatch.prettyPrint());

            //超过10秒的事务，报警
            if(stopWatch.getTotalTimeSeconds() > 10){
                SysRunlogWarningDto sysRunlogWarningDto = new SysRunlogWarningDto();
                sysRunlogWarningDto.setText("超过10秒的请求事务监控！\n类名：" + target.getClass().getName() +"\n方法：" + methodName + "\n耗时：" + stopWatch.getTotalTimeSeconds());
                UzaiRespVo<Object> objectUzaiRespVo = uzaiManageFeignService.sysRunlogWarning(sysRunlogWarningDto);
                logger.info("--调用官方钉钉报警事务超过10秒未处理完成的接口---para={},result={}", JSONObject.toJSONString(sysRunlogWarningDto), JSONObject.toJSONString(objectUzaiRespVo));
            }
        }
        return result;
    }

}
